#!/bin/sh

TOP_LEFT_CORNER='╔'
TOP_RIGHT_CORNER='╗'
BOTTOM_LEFT_CORNER='╚'
BOTTOM_RIGHT_CORNER='╝'
HORIZONTAL_LINE='═'
VERTICAL_LINE='║'

MENU_COLOR=`echo -en '\033[97;44m'` # blue bg color bright white fg

KEY_UP=`echo -en '\033[A'`
KEY_DOWN=`echo -en '\033[B'`
KEY_ESC=`echo -en '\033\033'`

decode_entry() {
 PDEV1=""
 PDRV=""
 PFIX=""
 PIMOD=""
 PMEDIA=""
 PSAVE=""
 PSAVEMARK=""
 PSAVEMENU=""
 PSUBDIR=""
 PUPSFS=""
 UNDERDOG=""
 ZDRV=""
 FDRV=""
 ADRV=""
 YDRV=""
 SEARCH_DIR=""
 SEARCH_DRIVE=""
 DISTRO_SPECS=""

 while true
 do
  ENTRY_PART=${CHOSEN_ENTRY%%|*}
  CHOSEN_ENTRY=${CHOSEN_ENTRY#*|}
  [ "$CHOSEN_ENTRY" = "$ENTRY_PART" ] && CHOSEN_ENTRY='' # EOF
  [ -z "$ENTRY_PART" -a -n "$CHOSEN_ENTRY" ] && continue
  #echo "$ENTRY_PART"

  [ "${ENTRY_PART#LABEL}" != "$ENTRY_PART" ] && continue # ignore LABEL


  case "$ENTRY_PART" in

   PDEV1*)
    trim_token "${ENTRY_PART#PDEV1}"
    PDEV1=${TRIM_TOKEN_RET}
    #echo "PDEV1 = $PDEV1"
   ;;

   PDRV*)
    trim_token "${ENTRY_PART#PDRV}"
    PDRV=${TRIM_TOKEN_RET}
    #echo "PDRV = $PDRV"
   ;;

   PFIX*)
    trim_token "${ENTRY_PART#PFIX}"
    PFIX=${TRIM_TOKEN_RET}
    #echo "PFIX = $PFIX"
   ;;

   # I think it is short for Puppy Input MODules,
   PIMOD*) # nothing to do with Raspberry Pi.
    trim_token "${ENTRY_PART#PIMOD}"
    PIMOD=${TRIM_TOKEN_RET}
    #echo "PIMOD = $PIMOD"
   ;;

   PMEDIA*)
    trim_token "${ENTRY_PART#PMEDIA}"
    PMEDIA=${TRIM_TOKEN_RET}
    #echo "PMEDIA = $PMEDIA"
   ;;

   PSAVE*)
    trim_token "${ENTRY_PART#PSAVE}"
    PSAVE=${TRIM_TOKEN_RET}
    #echo "PSAVE = $PSAVE"
   ;;

   PSAVEMARK*)
    trim_token "${ENTRY_PART#PSAVEMARK}"
    PSAVEMARK=${TRIM_TOKEN_RET}
    #echo "PSAVEMARK = $PSAVEMARK"
   ;;

   PSAVEMENU*)
    trim_token "${ENTRY_PART#PSAVEMENU}"
    PSAVEMENU=${TRIM_TOKEN_RET}
    #echo "PSAVEMENU = $PSAVEMENU"
   ;;

   PSUBDIR*)
    trim_token "${ENTRY_PART#PSUBDIR}"
    PSUBDIR=${TRIM_TOKEN_RET}
    #echo "PSUBDIR = $PSUBDIR"
   ;;

   PUPSFS*)
    trim_token "${ENTRY_PART#PUPSFS}"
    PUPSFS=${TRIM_TOKEN_RET}
    #echo "PUPSFS = $PUPSFS"
   ;;

   UNDERDOG*)
    trim_token "${ENTRY_PART#UNDERDOG}"
    UNDERDOG=${TRIM_TOKEN_RET}
    #echo "UNDERDOG = $UNDERDOG"
   ;;

   ZDRV*)
    trim_token "${ENTRY_PART#ZDRV}"
    ZDRV=${TRIM_TOKEN_RET}
    #echo "ZDRV = $ZDRV"
   ;;

   FDRV*)
    trim_token "${ENTRY_PART#FDRV}"
    FDRV=${TRIM_TOKEN_RET}
    #echo "FDRV = $FDRV"
   ;;

   ADRV*)
    trim_token "${ENTRY_PART#ADRV}"
    ADRV=${TRIM_TOKEN_RET}
    #echo "ADRV = $ADRV"
   ;;

   YDRV*)
    trim_token "${ENTRY_PART#YDRV}"
    YDRV=${TRIM_TOKEN_RET}
    #echo "YDRV = $YDRV"
   ;;

   SEARCH_DIR*)
    trim_token "${ENTRY_PART#SEARCH_DIR}"
    SEARCH_DIR=${TRIM_TOKEN_RET}
    #echo "SEARCH_DIR = $SEARCH_DIR"
   ;;

   SEARCH_DRIVE*)
    trim_token "${ENTRY_PART#SEARCH_DRIVE}"
    SEARCH_DRIVE=${TRIM_TOKEN_RET}
    #echo "SEARCH_DRIVE = $SEARCH_DRIVE"
   ;;

   DISTRO_SPECS*)
    trim_token "${ENTRY_PART#DISTRO_SPECS}"
    DISTRO_SPECS=${TRIM_TOKEN_RET}
    #echo "DISTRO_SPECS = $DISTRO_SPECS"
   ;;

   *)
    while [ "${ENTRY_PART:0:1}" = " " -o "${ENTRY_PART:0:1}" = "	" ]
    do
     ENTRY_PART=${ENTRY_PART# } # remove any leading spaces
     ENTRY_PART=${ENTRY_PART#	} # remove any leading tabs
    done
    [ -n "$ENTRY_PART" ] && echo "Ignoring unknown keyword: $ENTRY_PART"
   ;;
  esac

  [ -z "$CHOSEN_ENTRY" ] && break
 done
}

draw_screen() {
 echo -en '\033[s' # save cursor position

 echo -en '\033[2J' # clear screen
 echo -en "\033[${MENU_ROW_START};${MENU_COLUMN_START}H" # goto menu start
 CURRENT_ROW=${MENU_ROW_START}
 CURRENT_COLUMN=${MENU_COLUMN_START}

 echo -n "$MENU_COLOR"
 echo -n "$TOP_LEFT_CORNER"
 let MENU_COLUMN_END=MENU_COLUMN_START+MAX_LABEL_WIDTH+2
 while [ "$CURRENT_COLUMN" -lt "$MENU_COLUMN_END" ]
 do
  echo -n "$HORIZONTAL_LINE"
  let CURRENT_COLUMN++
 done
 echo "$TOP_RIGHT_CORNER"

 echo -en "\033[${MENU_COLUMN_START}G" # move to MENU_COLUMN_START
 CURRENT_COLUMN=${MENU_COLUMN_START}

 CURRENT_ENTRY_NR=0
 TEMP_ALL_ENTRIES=${ALL_ENTRIES}
 while true
 do
  ONE_ENTRY=${TEMP_ALL_ENTRIES%%'
'*}
  TEMP_ALL_ENTRIES=${TEMP_ALL_ENTRIES#*'
'}
  [ "$TEMP_ALL_ENTRIES" = "$ONE_ENTRY" ] && TEMP_ALL_ENTRIES='' # EOF
  [ -z "$ONE_ENTRY" -a -n "$TEMP_ALL_ENTRIES" ] && continue

  let CURRENT_ENTRY_NR++

  if [ "${ONE_ENTRY#LABEL}" != "$ONE_ENTRY" ]; then
   ECHO_STRING=${ONE_ENTRY%%|*}
   ECHO_STRING=${ECHO_STRING:6}
  else
   ECHO_STRING=${ONE_ENTRY%%|*}
  fi

  echo -n "$VERTICAL_LINE"
  if [ "$CURRENT_ENTRY_NR" = "$CHOSEN_ENTRY_NR" ]; then
   CHOSEN_ENTRY=${ONE_ENTRY}
   echo -ne '\033[7m' # reverse video
  fi
  echo -n " $ECHO_STRING"
  let CURRENT_COLUMN=CURRENT_COLUMN+${#ECHO_STRING}+1
  while [ "$CURRENT_COLUMN" -lt "$MENU_COLUMN_END" ]
  do
   echo -n " "
   let CURRENT_COLUMN++
  done
  [ "$CURRENT_ENTRY_NR" = "$CHOSEN_ENTRY_NR" ] && echo -ne '\033[27m' # reset reverse video
  echo "$VERTICAL_LINE"

  echo -en "\033[${MENU_COLUMN_START}G" # move to MENU_COLUMN_START
  CURRENT_COLUMN=${MENU_COLUMN_START}

  [ -z "$TEMP_ALL_ENTRIES" ] && break
 done

 echo -n "$BOTTOM_LEFT_CORNER"
 let MENU_COLUMN_END=MENU_COLUMN_START+MAX_LABEL_WIDTH+2
 while [ "$CURRENT_COLUMN" -lt "$MENU_COLUMN_END" ]
 do
  echo -n "$HORIZONTAL_LINE"
  let CURRENT_COLUMN++
 done
 echo "$BOTTOM_RIGHT_CORNER"
 echo -en '\033[0m' # reset color

 echo -en '\033[u' # restore cursor position
 echo -en '\033[10D' # backup cursor position
}

exec_init() {

 export pdev1=$PDEV1
 export pdrv=$PDRV
 export pfix=$PFIX
 export pimod=$PIMOD
 export pmedia=$PMEDIA
 export psave=$PSAVE
 export psavemark=$PSAVEMARK
 export psavemenu=$PSAVEMENU
 export psubdir=$PSUBDIR
 export pupsfs=$PUPSFS
 export underdog=$UNDERDOG
 export zdrv=$ZDRV
 export fdrv=$FDRV
 export adrv=$ADRV
 export ydrv=$YDRV

 export BOOTMENU_DONE=true
 sync
 [ -d "/proc/bus/usb" ] && umount /proc/bus/usb
 umount /sys
 umount /dev
 umount /proc
 # I don't want to exec the system init while testing...
 exec ./init
}

show_menu() {
 let MENU_ROW_START=ROWS-ENTRY_COUNT
 let MENU_ROW_START=MENU_ROW_START/2
 #echo "MENU_ROW_START = $MENU_ROW_START"

 let MENU_COLUMN_START=COLUMNS-MAX_LABEL_WIDTH
 let MENU_COLUMN_START=MENU_COLUMN_START/2
 #echo "MENU_COLUMN_START = $MENU_COLUMN_START"

 [ -z "$CHOSEN_ENTRY_NR" ] && CHOSEN_ENTRY_NR=1

 while true
 do
  draw_screen

  local TEMP_INPUT=""
  local INPUT=""
  while true
  do
   if [ -z "$TIMEOUT" ]; then
    read -n1 INPUT
   else
    read -n1 -t $TIMEOUT INPUT
    TIMEOUT=""
   fi
   [ "$INPUT" = "" ] && break

   TEMP_INPUT=${TEMP_INPUT}${INPUT}
   [ "${#TEMP_INPUT}" -gt 3 ] && TEMP_INPUT=${TEMP_INPUT:1}

   # Because arrow key codes start with the ESC charactor, ESC must be pressed
   # twice to exit menu.  KEY_ESC = '\033\033', two ESC chars in a row.
   [ "${TEMP_INPUT}" = "$KEY_ESC" ] && INPUT="" && CHOSEN_ENTRY="" && break
   [ "${TEMP_INPUT:1}" = "$KEY_ESC" ] && INPUT="" && CHOSEN_ENTRY="" && break

   [ "$TEMP_INPUT" = "$KEY_UP"  -a "$CHOSEN_ENTRY_NR" -gt 1 ] && let CHOSEN_ENTRY_NR-- && draw_screen
   [ "$TEMP_INPUT" = "$KEY_DOWN"  -a "$CHOSEN_ENTRY_NR" -lt "$ENTRY_COUNT" ] && let CHOSEN_ENTRY_NR++ && draw_screen

  done
  [ "$INPUT" = "" ] && break
 done
}

trim_token() {
 local TOKEN=${1}
 while [ "${TOKEN:0:1}" = " " -o "${TOKEN:0:1}" = "	" -o "${TOKEN:0:1}" = "=" ]
 do                                # This is a tab ^
  TOKEN=${TOKEN# } # remove any leading spaces
  TOKEN=${TOKEN#	} # remove any leading tabs
  TOKEN=${TOKEN#=} # remove any leading '='
 done
 while [ "${TOKEN% }" != "$TOKEN" -o "${TOKEN%	}" != "$TOKEN" ]
 do
  TOKEN=${TOKEN% } # remove any trailing spaces
  TOKEN=${TOKEN%	} # remove any trailing tabs
 done
 TRIM_TOKEN_RET=${TOKEN//\"} # remove any '"' chars
}
